package com.guoranhao.tool.utils;

import com.guoranhao.tool.constants.BaseErrorCodeEnum;
import com.guoranhao.tool.enums.FileUploadSourceEnum;
import com.guoranhao.tool.vo.MessageVo;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Map;

/**
 * Description:
 * All Rights Reserved.
 *
 * @version 1.0  2017/9/21 15:34  by  马双亮（masl@cloud-young.com）创建
 */
public class FileUploadUtil {

    private static final Logger logger = LoggerFactory.getLogger(FileUploadUtil.class);

    public static MessageVo<String> uploadImg2OSSDefault(int source, InputStream in) {
        String fileName = "";
        return uploadImgWithFileName2OSSDefault(source, fileName, in);
    }

    public static MessageVo<String>  uploadImgWithFileName2OSSDefault(int source, String fileName, InputStream in) {

        long tid = System.currentTimeMillis();
        if (!FileUploadSourceEnum.checkSource(source) || in == null) {
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100001.getCode(), BaseErrorCodeEnum.ERRCODE_100001.getMsg() + ":数据来源，图片流均不能为空！");
        }
        //上传前先转byte，防止上传失败后流被关闭,无法重试
        byte[] inByte = input2byte(in);
        //获取图片后缀
        String fileType = FileValidator.getTypeByStream(new ByteArrayInputStream(inByte));
        logger.info("uploadImg2OSSDefault-" + tid + "-图片上传开始,入参source:{},fileType:{}", source, fileType);
        String url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), tid);
        if (StringUtils.isEmpty(url)) {
            //上传第一次失败
            logger.warn("uploadImg2OSSDefault-" + tid + "-图片上传第一次失败，开始进行第二次！");
            url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), tid);
        }
        if (StringUtils.isEmpty(url)) {
            //上传第二次失败
            logger.warn("uploadImg2OSSDefault-" + tid + "-图片上传第二次失败，开始进行第三次！");
            url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), tid);
        }
        if (StringUtils.isEmpty(url)) {
            //上传第三次失败
            logger.warn("uploadImg2OSSDefault-" + tid + "-图片上传第三次失败，提示失败！");
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100003.getCode(), BaseErrorCodeEnum.ERRCODE_100003.getMsg());
        }
        logger.info("uploadImg2OSSDefault-" + tid + "-图片上传结束,出参{}", url);
        return new MessageVo<String>(true, url);
    }

    public static MessageVo<String> uploadImg2OSSByConfig(int source, Map<String, String> map, InputStream in) {
        String fileName = "";
        long tid = System.currentTimeMillis();
        //上传图片默认png
        String fileType = "png";
        if (null == map || !FileUploadSourceEnum.checkSource(source) || null == in) {
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100001.getCode(), BaseErrorCodeEnum.ERRCODE_100001.getMsg() + ":配置信息,数据来源,图片流均不能为空！");
        }
        logger.info("uploadImg2OSSByConfig-" + tid + "-图片上传开始,入参source:" + source + ",fileType:" + fileType + ",map:" + com.alibaba.fastjson.JSON.toJSONString(map));
        //上传前先转byte，防止上传失败后流被关闭,无法重试
        byte[] inByte = input2byte(in);
        String url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), map, tid);
        if (StringUtils.isEmpty(url)) {
            //上传第一次失败
            logger.warn("uploadImg2OSSByConfig-" + tid + "-图片上传第一次失败，开始进行第二次！");
            url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), map, tid);
        }
        if (StringUtils.isEmpty(url)) {
            //上传第二次失败
            logger.warn("uploadImg2OSSByConfig-" + tid + "-图片上传第二次失败，开始进行第三次！");
            url = OssFileUtils.uploadFile(source, fileName, fileType, new ByteArrayInputStream(inByte), map, tid);
        }
        if (StringUtils.isEmpty(url)) {
            //上传第三次失败
            logger.warn("uploadImg2OSSByConfig-" + tid + "-图片上传第三次失败，提示失败！");
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100003.getCode(), BaseErrorCodeEnum.ERRCODE_100003.getMsg());
        }
        logger.info("uploadImg2OSSByConfig-" + tid + "-图片上传结束,出参{}", url);
        return new MessageVo<String>(true, url);
    }

    public static MessageVo<String> uploadFile2OSSDefault(int source, String fileType, InputStream in) {
        String fileName = "";
        long tid = System.currentTimeMillis();
        if (!FileUploadSourceEnum.checkSource(source) || StringUtils.isEmpty(fileType) || null == in) {
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100001.getCode(), BaseErrorCodeEnum.ERRCODE_100001.getMsg() + ":数据来源,文件类型，图片流均不能为空！");
        }
        logger.info("uploadFile2OSSDefault-" + tid + "-文件上传开始,入参source:{},fileType:{}", source, fileType);
        String url = OssFileUtils.uploadFile(source, fileName, fileType, in, tid);
        if (StringUtils.isEmpty(url)) {
            //上传失败
            logger.warn("uploadFile2OSSDefault-" + tid + "-文件上传失败，提示失败！");
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100003.getCode(), BaseErrorCodeEnum.ERRCODE_100003.getMsg());
        }
        logger.info("uploadFile2OSSDefault-" + tid + "-文件上传结束,出参{}", url);
        return new MessageVo<String>(true, url);
    }

    public static MessageVo<String> uploadFile2OSSByConfig(int source, String fileType, Map<String, String> map, InputStream in) {
        String fileName = "";
        long tid = System.currentTimeMillis();
        if (null == map || !FileUploadSourceEnum.checkSource(source) || StringUtils.isEmpty(fileType) || null == in) {
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100001.getCode(), BaseErrorCodeEnum.ERRCODE_100001.getMsg()+ ":配置信息,数据来源,文件类型，图片流均不能为空！");
        }
        logger.info("uploadFile2OSSByConfig-" + tid + "-文件上传开始,入参source:" + source + ",fileType:" + fileType + ",map:" + com.alibaba.fastjson.JSON.toJSONString(map));
        String url = OssFileUtils.uploadFile(source, fileName, fileType, in, map, tid);
        if (StringUtils.isEmpty(url)) {
            //上传失败
            logger.warn("uploadFile2OSSByConfig-" + tid + "-文件上传失败，提示失败！");
            return new MessageVo<String>(false, BaseErrorCodeEnum.ERRCODE_100003.getCode(), BaseErrorCodeEnum.ERRCODE_100003.getMsg());
        }
        logger.info("uploadFile2OSSByConfig-" + tid + "-文件上传结束,出参{}", url);
        return new MessageVo<String>(true,url);
    }

    public static MessageVo<String> uploadImg2OSSDefaultForWZ(int source, InputStream in) {
        String fileName = "";
        MessageVo<String> result = uploadImgWithFileName2OSSDefault(source, fileName, in);
        if (result.getResult() && StringUtils.isNotEmpty(result.getData())) {
            result.setData(FileUrlUtils.addPrefix(result.getData()));
        }
        return result;
    }

    public static final byte[] input2byte(InputStream inStream) {
        ByteArrayOutputStream swapStream = new ByteArrayOutputStream();
        byte[] buff = new byte[100];
        int rc = 0;
        byte[] in2b = null;
        try {
            while ((rc = inStream.read(buff, 0, 100)) > 0) {
                swapStream.write(buff, 0, rc);
            }
            in2b = swapStream.toByteArray();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                swapStream.close();
                inStream.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return in2b;
    }


}
